/**
 * 
 */
package com.google.code.cisx.servlets;

import com.google.code.cisx.client.dto.BuildDefinitionTemplateViewHelper;
import com.google.code.cisx.client.dto.BuildDefinitionViewHelper;
import com.google.code.cisx.client.dto.BuildResultViewHelper;
import com.google.code.cisx.client.dto.ChangeFileViewHelper;
import com.google.code.cisx.client.dto.ChangeSetViewHelper;
import com.google.code.cisx.client.dto.ProjectDependencyViewHelper;
import com.google.code.cisx.client.dto.ProjectDeveloperViewHelper;
import com.google.code.cisx.client.dto.ProjectGroupViewHelper;
import com.google.code.cisx.client.dto.ProjectNotifierViewHelper;
import com.google.code.cisx.client.dto.ProjectViewHelper;
import com.google.code.cisx.client.dto.ScheduleViewHelper;
import com.google.code.cisx.client.dto.ScmResultViewHelper;
import com.google.code.cisx.client.dto.SuiteResultViewHelper;
import com.google.code.cisx.client.dto.TestCaseFailureViewHelper;
import com.google.code.cisx.client.dto.TestResultViewHelper;
import com.google.code.cisx.converters.BeanUtilsBeanExtended;
import com.google.code.cisx.converters.BuildDefinitionConverter;
import com.google.code.cisx.converters.BuildDefinitionTemplateConverter;
import com.google.code.cisx.converters.BuildResultConverter;
import com.google.code.cisx.converters.ConvertUtilsBeanExtended;
import com.google.code.cisx.converters.ProjectConverter;
import com.google.code.cisx.converters.ProjectDependencyConverter;
import com.google.code.cisx.converters.ProjectDeveloperConverter;
import com.google.code.cisx.converters.ProjectGroupConverter;
import com.google.code.cisx.converters.ProjectNotifierConverter;
import com.google.code.cisx.converters.ScheduleConverter;
import com.google.code.cisx.converters.scm.ChangeFileConverter;
import com.google.code.cisx.converters.scm.ChangeSetConverter;
import com.google.code.cisx.converters.scm.ScmResultConverter;
import com.google.code.cisx.converters.scm.SuiteResultConverter;
import com.google.code.cisx.converters.scm.TestCaseFailureConverter;
import com.google.code.cisx.converters.scm.TestResultConverter;
import com.google.code.cisx.model.project.BuildDefinitionTemplate;
import com.google.code.cisx.model.project.BuildResult;
import com.google.code.cisx.model.project.Project;
import com.google.code.cisx.model.project.ProjectDependency;
import com.google.code.cisx.model.project.ProjectDeveloper;
import com.google.code.cisx.model.project.ProjectGroup;
import com.google.code.cisx.model.project.ProjectNotifier;
import com.google.code.cisx.model.project.Schedule;
import com.google.code.cisx.model.scm.ChangeFile;
import com.google.code.cisx.model.scm.ChangeSet;
import com.google.code.cisx.model.scm.ScmResult;
import com.google.code.cisx.model.scm.SuiteResult;
import com.google.code.cisx.model.scm.TestCaseFailure;
import com.google.code.cisx.model.scm.TestResult;

import org.apache.commons.beanutils.ConvertUtils;
import org.apache.commons.beanutils.PropertyUtilsBean;
import org.apache.commons.beanutils.converters.DateConverter;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;

import java.util.Date;

import javax.servlet.Servlet;
import javax.servlet.ServletConfig;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;

/**
 * StartupServlet starts up when the cisx web app is started by the JEE
 * Container. The purpose of this is servlet is to configure the cisx
 * application.
 * 
 * @author <a href='mailto:rahul.thakur.xdev@gmail.com'>Rahul Thakur</a>
 * @since 1.0
 * @version $Id: StartupServlet.java 258 2008-11-29 06:23:51Z rahul.thakur.xdev $
 */
public final class StartupServlet extends HttpServlet implements Servlet {

  /**
   * 
   */
  private static final long serialVersionUID = 8204300626644376608L;

  /**
   * Commons Logging.
   */
  private static final Log log = LogFactory.getLog(StartupServlet.class);

  /**
   * Convert Utility Bean.
   */
  private static final ConvertUtilsBeanExtended convertUtilsBean = new ConvertUtilsBeanExtended();

  /**
   * Property Utillity Bean.
   */
  private static final PropertyUtilsBean propertyUtilsBean = new PropertyUtilsBean();

  /**
   * Bean Utils bean that utilizes the {@link #convertUtilsBean} and
   * {@link #propertyUtilsBean}
   */
  private static final BeanUtilsBeanExtended beanUtilsBean = new BeanUtilsBeanExtended(
      convertUtilsBean, propertyUtilsBean);

  /**
   * @see Servlet#init(ServletConfig)
   */
  public void init(ServletConfig config) throws ServletException {
    super.init();
    if (log.isInfoEnabled())
      log.info("Registering DTO <--> JPA entity converters with "
          + ConvertUtils.class.getSimpleName());

    registerBeanConverters();

    if (log.isInfoEnabled())
      log.info("DTO <--> JPA entity registration completed!");
  }

  /**
   * 
   */
  private void registerBeanConverters() {
    BuildDefinitionConverter buildDefinitionConverter = new BuildDefinitionConverter(beanUtilsBean);
    convertUtilsBean.register(buildDefinitionConverter, BuildDefinitionViewHelper.class);
    convertUtilsBean.register(buildDefinitionConverter, BuildDefinitionViewHelper.class);

    BuildDefinitionTemplateConverter buildDefinitionTemplateConverter = new BuildDefinitionTemplateConverter(
        beanUtilsBean);
    convertUtilsBean.register(buildDefinitionTemplateConverter,
        BuildDefinitionTemplateViewHelper.class);
    convertUtilsBean.register(buildDefinitionTemplateConverter, BuildDefinitionTemplate.class);

    BuildResultConverter buildResultConverter = new BuildResultConverter(beanUtilsBean);
    convertUtilsBean.register(buildResultConverter, BuildResultViewHelper.class);
    convertUtilsBean.register(buildResultConverter, BuildResult.class);

    ProjectConverter projectConverter = new ProjectConverter(beanUtilsBean);
    convertUtilsBean.register(projectConverter, ProjectViewHelper.class);
    convertUtilsBean.register(projectConverter, Project.class);

    ProjectDependencyConverter projectDependencyConverter = new ProjectDependencyConverter(
        beanUtilsBean);
    convertUtilsBean.register(projectDependencyConverter, ProjectDependencyViewHelper.class);
    convertUtilsBean.register(projectDependencyConverter, ProjectDependency.class);

    ProjectDeveloperConverter projectDeveloperConverter = new ProjectDeveloperConverter(
        beanUtilsBean);
    convertUtilsBean.register(projectDeveloperConverter, ProjectDeveloperViewHelper.class);
    convertUtilsBean.register(projectDeveloperConverter, ProjectDeveloper.class);

    ProjectGroupConverter projectGroupConverter = new ProjectGroupConverter(beanUtilsBean);
    convertUtilsBean.register(projectGroupConverter, ProjectGroupViewHelper.class);
    convertUtilsBean.register(projectGroupConverter, ProjectGroup.class);

    ProjectNotifierConverter projectNotifierConverter = new ProjectNotifierConverter(beanUtilsBean);
    convertUtilsBean.register(projectNotifierConverter, ProjectNotifierViewHelper.class);
    convertUtilsBean.register(projectNotifierConverter, ProjectNotifier.class);

    ScheduleConverter scheduleConverter = new ScheduleConverter(beanUtilsBean);
    convertUtilsBean.register(scheduleConverter, ScheduleViewHelper.class);
    convertUtilsBean.register(scheduleConverter, Schedule.class);

    ChangeFileConverter changeFileConverter = new ChangeFileConverter(beanUtilsBean);
    convertUtilsBean.register(changeFileConverter, ChangeFileViewHelper.class);
    convertUtilsBean.register(changeFileConverter, ChangeFile.class);

    ChangeSetConverter changeSetConverter = new ChangeSetConverter(beanUtilsBean);
    convertUtilsBean.register(changeSetConverter, ChangeSetViewHelper.class);
    convertUtilsBean.register(changeSetConverter, ChangeSet.class);

    ScmResultConverter ScmResultConverter = new ScmResultConverter(beanUtilsBean);
    convertUtilsBean.register(ScmResultConverter, ScmResultViewHelper.class);
    convertUtilsBean.register(ScmResultConverter, ScmResult.class);

    SuiteResultConverter SuiteResultConverter = new SuiteResultConverter(beanUtilsBean);
    convertUtilsBean.register(SuiteResultConverter, SuiteResultViewHelper.class);
    convertUtilsBean.register(SuiteResultConverter, SuiteResult.class);

    TestCaseFailureConverter TestCaseFailureConverter = new TestCaseFailureConverter(beanUtilsBean);
    convertUtilsBean.register(TestCaseFailureConverter, TestCaseFailureViewHelper.class);
    convertUtilsBean.register(TestCaseFailureConverter, TestCaseFailure.class);

    TestResultConverter TestResultConverter = new TestResultConverter(beanUtilsBean);
    convertUtilsBean.register(TestResultConverter, TestResultViewHelper.class);
    convertUtilsBean.register(TestResultConverter, TestResult.class);

    convertUtilsBean.deregister(Date.class);
    DateConverter dateConverter = new DateConverter(new Date());
    convertUtilsBean.register(dateConverter, Date.class);
  }

  /**
   * Convenience to share the {@link BeanUtilsBeanExtended} with all servlets.
   * 
   * @return
   */
  public static BeanUtilsBeanExtended getBeanUtilsBean() {
    return beanUtilsBean;
  }

}
